package com.jsb.laundry.service.impl;

import com.jsb.laundry.common.constant.CommonConstants;
import com.jsb.laundry.common.design_service.pay.properties.WechatMiniPayProperties;
import com.jsb.laundry.common.enums.ReturnStatusCode;
import com.jsb.laundry.common.exception.BusinessException;
import com.jsb.laundry.common.utils.id.IDUtil;
import com.jsb.laundry.common.utils.redis.RedisUtil;
import com.jsb.laundry.controller.OrderController;
import com.jsb.laundry.dao.CouponDao;
import com.jsb.laundry.model.dto.ProductInfoMapDto;
import com.jsb.laundry.model.entity.CouponUserBag;
import com.jsb.laundry.model.vo.PrePayVo;
import com.jsb.laundry.service.CouponService;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import java.time.LocalDate;
import java.time.ZoneId;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Date;
import java.util.List;
import java.util.concurrent.CopyOnWriteArrayList;
import java.util.concurrent.TimeUnit;

@Service
public class CouponServiceImpl implements CouponService {

    @Resource
    private WechatMiniPayProperties wechatMiniPayProperties;
    @Resource
    private CouponDao couponDao;

    @Resource
    private RedisUtil redisUtil;


    @Override
    public Object getCouponListByUserId(String userId, String useType, int currentNumber) {
        Date now = new Date();
        // 待使用(0) 已使用(1)
        if ("0".equals(useType) || "1".equals(useType)) {
            List<CouponUserBag> var0 = couponDao.findCurrentMonthCoupon(userId, useType, new Date());
            return var0;
        } else if ("2".equals(useType)) { //待领取(2)
            List<CouponUserBag> var1 = couponDao.findCurrentPreReceiveCoupon(userId);
            long timeStamp3 = 3 * 24 * 60 * 60 * 1000; //3天的时间戳
            for (CouponUserBag couponRecord : var1) {
                couponRecord.setExpirationTimeStamp(couponRecord.getExpirationTime().getTime() + timeStamp3); //待领取优惠券失效时间
            }
            return var1;
        } else { //待发放(3)
            if (currentNumber <= 0) {
                currentNumber = 0;
            }
            int tcNumber = 0;

            List<CouponUserBag> currentMonthCoupon = couponDao.getAvailableCouponInfo(userId, useType);
            if (currentMonthCoupon.size() == 0) {
                return new ArrayList();
            }

            if ("tc1".equals(currentMonthCoupon.get(0).getTcId())) { //套餐1
                tcNumber = currentMonthCoupon.size() < 5 ? currentMonthCoupon.size() : 5;
            } else if ("tc2".equals(currentMonthCoupon.get(0).getTcId())) {//套餐2
                tcNumber = currentMonthCoupon.size() < 3 ? currentMonthCoupon.size() : 3;
            }

            List<CouponUserBag> var2 = currentMonthCoupon.subList(currentNumber * tcNumber, (currentNumber + 1) * tcNumber);
            for (CouponUserBag coupon : var2) {
                if (now.getTime() > coupon.getEndTime().getTime() && coupon.getUseTime() == null) { //已过期
                    coupon.setCouponStatus("2");
                } else if (now.getTime() > coupon.getBeginTime().getTime() && now.getTime() < coupon.getEndTime().getTime() && coupon.getUseTime() == null) { //未使用
                    coupon.setCouponStatus("0");
                } else if (now.getTime() > coupon.getBeginTime().getTime() && now.getTime() < coupon.getEndTime().getTime() && coupon.getUseTime() != null) { //已使用
                    coupon.setCouponStatus("1");
                } else {// 3:待发放 //if (now.getTime() < coupon.getBeginTime().getTime())
                    coupon.setCouponStatus("3");
                }
            }
            return var2;
        }
    }


    /**
     * vip购买时数据入库
     *
     * @param couponUserBag
     * @return
     */
    @Transactional
    @Override
    public PrePayVo vipDataSave(CouponUserBag couponUserBag) {
        String userId = couponUserBag.getUserId();
        String tcId = couponUserBag.getTcId();

        //获取套餐价格 和 openid
        CouponUserBag priceAndOpenId = couponDao.getCouponPackagePriceAndOpenId(userId, tcId);

        int couponPackageMoney = priceAndOpenId.getPrice();

        /**
         * TODO 订单id生成
         */
        String orderId = CommonConstants.VIP_ORDER_PREFIX + IDUtil.getPayId();
        couponUserBag.setPayId(orderId);
        //购买优惠券预下单一年的数据入库
        int i = couponPreBuy(couponUserBag);
        //用户购买优惠券订单
        int j = couponDao.addCouponUserBuy(userId, tcId, orderId);
        if (i == 0 || j == 0) {//未添加成功
            throw new BusinessException(ReturnStatusCode.SAVE_ERROR);
        }

        PrePayVo prePayVo = new PrePayVo().setOrderId(orderId).setUserId(userId);

        //把实际支付金额存入redis中
        ProductInfoMapDto productInfoMapDto = new ProductInfoMapDto();
        productInfoMapDto.setUserId(userId).setOrderId(orderId)
                .setTotal(couponPackageMoney).setProductType(OrderController.getProductType(Arrays.asList(tcId)))
                .setCallbackUrl(wechatMiniPayProperties.getLaundryCallbackUrlVip());
        redisUtil.setCacheObject(CommonConstants.TIMEOUT30_WAIT_PAY_ORDER + orderId, productInfoMapDto, 30, TimeUnit.MINUTES);

        return prePayVo;
    }

    /**
     * 购买优惠券预下单数据入库
     *
     * @param couponRecord
     * @return
     */
    public int couponPreBuy(CouponUserBag couponRecord) {
        //查询套餐下的优惠券
        List<CouponUserBag> couponRecordList = couponDao.findCouponPackageList(couponRecord.getTcId());
        for (CouponUserBag record : couponRecordList) {
            record.setUserId(couponRecord.getUserId());
            record.setPayId(couponRecord.getPayId());
        }
        //构建套餐对应的一年的数据
        List<CouponUserBag> list = couponBuild(couponRecordList);
        int num = couponDao.couponPreBuy(list); //批量插入
        return num;
    }

    /**
     * 根据套餐类型构建对应的所有数据
     *
     * @return
     */
    public static List<CouponUserBag> couponBuild(List<CouponUserBag> couponRecordList) {
        List<CouponUserBag> list = new CopyOnWriteArrayList<>();
        LocalDate date = LocalDate.now(); // 获取当前日期

        //构建一年的优惠券
        for (int k = 0; k < 12; k++) {

            //一个月的优惠券
            for (CouponUserBag couponRecord : couponRecordList) {
                for (int i = 0; i < couponRecord.getCouponNum(); i++) {
                    CouponUserBag var0 = new CouponUserBag();
                    var0.setUserId(couponRecord.getUserId());
                    var0.setCouponId(couponRecord.getCouponId());
                    var0.setPayId(couponRecord.getPayId());
                    var0.setTcId(couponRecord.getTcId());

                    Date startTime = Date.from(date.atStartOfDay(ZoneId.systemDefault()).toInstant());
                    var0.setBeginTime(startTime);
                    Date endTime = Date.from(date.plusMonths(1).atStartOfDay(ZoneId.systemDefault()).toInstant());// 添加一个月
                    var0.setEndTime(endTime);

                    list.add(var0);
                }
            }

            date = date.plusMonths(1);
        }
        return list;
    }


}
